﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Globalization;
using System.Linq;
using System.Windows;
using System.Windows.Media;
using EveMarkets.UserControls;
using EveMarketsDAO;

namespace EveMarkets
{
	/// <summary>
	/// Logique d'interaction pour VueGeographique.xaml
	/// </summary>
	public partial class VueGeographique : Window
	{
		private BackgroundWorker _workerRegionJump;
		private BackgroundWorker _workerRegionKill;

		private BackgroundWorker _workerSystemJump;
		private BackgroundWorker _workerSystemKill;

		#region Constructeurs
		/// <summary>
		/// Constructeur pour une windows "Systems"
		/// </summary>
		/// <param name="numeroItem"></param>
		/// <param name="nomGeographique"></param>
		public VueGeographique(int numeroItem, string nomGeographique)
		{
			InitializeComponent();
			InitializeBackgroundWorkerSystemsJump();
			InitializeBackgroundWorkerSystemsKill();

			this.Title = "All systems in " + nomGeographique;

			// Construction des userControls
			List<mapSolarSystems> listeSystems =
				ContexteDAO.ContexteDonnees.mapSolarSystems.Where(x => x.mapRegions.regionName.Equals(nomGeographique)).OrderBy(nomSys => nomSys.solarSystemName).ToList();

			foreach (var system in listeSystems)
			{
				UcMarketItem marketItem = new UcMarketItem(numeroItem, false, system.solarSystemID);
				marketItem.lblGeo.Content = system.solarSystemName;
				// Si la security est supérieur à 0.4, je met en vert.
				if (system.security > 0.4)
					marketItem.lblSecurity.Foreground = Brushes.Green;
				else
					marketItem.lblSecurity.Foreground = Brushes.Red;
				marketItem.lblSecurity.Content = (Math.Round(Convert.ToDouble(system.security.Value), 2)).ToString();
				wrapRoot.Children.Add(marketItem);
			}

			_workerSystemJump.RunWorkerAsync();
			_workerSystemKill.RunWorkerAsync();
		}
		private void InitializeBackgroundWorkerSystemsJump()
		{
			_workerSystemJump = new BackgroundWorker();
			_workerSystemJump.DoWork += new DoWorkEventHandler(backgroundWorkerSystemsJump_DoWork);
			_workerSystemJump.RunWorkerCompleted += new RunWorkerCompletedEventHandler(backgroundWorkerSystemsJump_RunWorkerCompleted);
		}
		private void InitializeBackgroundWorkerSystemsKill()
		{
			_workerSystemKill = new BackgroundWorker();
			_workerSystemKill.DoWork += new DoWorkEventHandler(backgroundWorkerSystemsKill_DoWork);
			_workerSystemKill.RunWorkerCompleted += new RunWorkerCompletedEventHandler(backgroundWorkerSystemsKill_RunWorkerCompleted);
		} 

		/// <summary>
		/// Constructeur pour une Windows "Region"
		/// </summary>
		/// <param name="numeroItem"></param>
		public VueGeographique(int numeroItem)
		{
			InitializeComponent();
			InitializeBackgroundWorkerJump();
			InitializeBackgroundWorkerKill();

			this.Title = "All Regions";

			// NOTE : Pour les tests.
			//UcMarketItem marketItem = new UcMarketItem(numeroItem, true, 10000002);
			//marketItem.lblGeo.Content = "The Forge";
			//marketItem.lblSecurity.Content = String.Empty;
			//wrapRoot.Children.Add(marketItem);

			// Construit tous les UserControls
			List<mapRegions> listeRegion = ContexteDAO.ContexteDonnees.mapRegions.Where(x => !x.regionName.Equals("Unknown")).OrderBy(nom => nom.regionName).ToList();

			foreach (var region in listeRegion)
			{
				UcMarketItem marketItem = new UcMarketItem(numeroItem, true, region.regionID);
				marketItem.lblGeo.Content = region.regionName;
				marketItem.lblSecurity.Content = String.Empty;
				wrapRoot.Children.Add(marketItem);
			}

			// Ensuite aller les chercher les informations sur EveOnline.
			_workerRegionJump.RunWorkerAsync();
			_workerRegionKill.RunWorkerAsync();
		}
		private void InitializeBackgroundWorkerJump()
		{
			_workerRegionJump = new BackgroundWorker();
			_workerRegionJump.DoWork += new DoWorkEventHandler(backgroundWorkerJump_DoWork);
			_workerRegionJump.RunWorkerCompleted += new RunWorkerCompletedEventHandler(backgroundWorkerJump_RunWorkerCompleted);
		}
		private void InitializeBackgroundWorkerKill()
		{
			_workerRegionKill = new BackgroundWorker();
			_workerRegionKill.DoWork += new DoWorkEventHandler(backgroundWorkerKill_DoWork);
			_workerRegionKill.RunWorkerCompleted += new RunWorkerCompletedEventHandler(backgroundWorkerKill_RunWorkerCompleted);
		} 
		#endregion

		#region Event BackgroundWorker Region

		/// <summary>
		/// 
		/// </summary>
		/// <param name="sender"></param>
		/// <param name="e"></param>
		private void backgroundWorkerJump_DoWork(object sender, DoWorkEventArgs e)
		{
			e.Result = InformationsMap.ContexteJump;
		}

		/// <summary>
		/// 
		/// </summary>
		/// <param name="sender"></param>
		/// <param name="e"></param>
		private void backgroundWorkerJump_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
		{
			// Il faut en résultats (nomRegion, (liste (nomSystem, nbreJump))
			EveIndusEntities nouveauCOntexte = new EveIndusEntities();
			SortedDictionary<int, int> listSystemJump = e.Result as SortedDictionary<int, int>;

			var listNomRegion_IdSystem = (from syst in nouveauCOntexte.mapSolarSystems
										  join region in nouveauCOntexte.mapRegions
											on syst.regionID equals region.regionID
										  where !region.regionName.Equals("Unknown")
										  select new
												  {
													  NomRegion = region.regionName,
													  numSystem = syst.solarSystemID,
													  NomSysteme = syst.solarSystemName
												  }).ToList();

			var listRegionSystemJump = (from dd in listSystemJump
						join proute in listNomRegion_IdSystem
							on dd.Key equals proute.numSystem
						select new
								{
									proute.NomRegion,
									proute.NomSysteme,
									nbreJump = dd.Value
								}).ToList();
			
			// Maintenant il faut mettre à jour tout les UserControls.
			// Pour chaque userControl
			foreach (var child in wrapRoot.Children)
			{
				var ucTest = child as UcMarketItem;

				var totalJump = listRegionSystemJump.Where(x => x.NomRegion.Equals(ucTest.lblGeo.Content)).Sum(y => y.nbreJump);
				ucTest.lblJump.Content = totalJump.ToString();

				ucTest.IsOkJump = true;

				if (ucTest.IsOkMarket && ucTest.IsOkKill && ucTest.IsOkJump)
					ucTest.IsEnabled = true;
			}
			
			
		}

		/// <summary>
		/// 
		/// </summary>
		/// <param name="sender"></param>
		/// <param name="e"></param>
		private void backgroundWorkerKill_DoWork(object sender, DoWorkEventArgs e)
		{
			//  solarSystemID="30001343" shipKills="0" factionKills="17" podKills="0" 
			e.Result = InformationsMap.ContexteMapKill;
		}

		/// <summary>
		/// 
		/// </summary>
		/// <param name="sender"></param>
		/// <param name="e"></param>
		private void backgroundWorkerKill_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
		{
			EveIndusEntities nouveauCOntexte = new EveIndusEntities();
			//  solarSystemID="30001343" shipKills="0" factionKills="17" podKills="0" 
			List<Tuple<int, int, int, int>> listSystemJump = e.Result as List<Tuple<int, int, int, int>>;

			var listNomRegionIdSystem = (from syst in nouveauCOntexte.mapSolarSystems
										  join region in nouveauCOntexte.mapRegions
							on syst.regionID equals region.regionID
										  where !region.regionName.Equals("Unknown")
										  select new
										  {
											  NomRegion = region.regionName,
											  numSystem = syst.solarSystemID,
											  NomSysteme = syst.solarSystemName
										  }).ToList();

			var listRegionSystemJump = (from dd in listSystemJump
										join proute in listNomRegionIdSystem
											on dd.Item1 equals proute.numSystem
										select new
										{
											proute.NomRegion,
											proute.NomSysteme,
											shipsKills = dd.Item2,
											npcKill = dd.Item3,
											podKill = dd.Item4
										}).ToList();

			// Maintenant il faut mettre à jour tout les UserControls.
			// Pour chaque userControl
			foreach (var child in wrapRoot.Children)
			{
				var ucTest = child as UcMarketItem;

				ucTest.lblShipKill.Content = listRegionSystemJump.Where(x => x.NomRegion.Equals(ucTest.lblGeo.Content)).Sum(y => y.shipsKills).ToString(CultureInfo.InvariantCulture);
				ucTest.lblNpcKill.Content = listRegionSystemJump.Where(x => x.NomRegion.Equals(ucTest.lblGeo.Content)).Sum(y => y.npcKill).ToString(CultureInfo.InvariantCulture);
				ucTest.lblPodKill.Content = listRegionSystemJump.Where(x => x.NomRegion.Equals(ucTest.lblGeo.Content)).Sum(y => y.podKill).ToString(CultureInfo.InvariantCulture);

				ucTest.IsOkKill = true;

				if (ucTest.IsOkMarket && ucTest.IsOkKill && ucTest.IsOkJump)
					ucTest.IsEnabled = true;
			}
		}

		#endregion

		#region Events BackgroundWorker Systems


		/// <summary>
		/// 
		/// </summary>
		/// <param name="sender"></param>
		/// <param name="e"></param>
		private void backgroundWorkerSystemsJump_DoWork(object sender, DoWorkEventArgs e)
		{
			e.Result = InformationsMap.ContexteJump;
		}

		/// <summary>
		/// 
		/// </summary>
		/// <param name="sender"></param>
		/// <param name="e"></param>
		private void backgroundWorkerSystemsJump_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
		{
			EveIndusEntities nouveauCOntexte = new EveIndusEntities();
			// int systemID, int nbreJump
			SortedDictionary<int, int> listSystemJump = e.Result as SortedDictionary<int, int>;

			var nomSysIdSys = (from sys in nouveauCOntexte.mapSolarSystems
			                   select new
			                          	{
			                          		NomSystem = sys.solarSystemName,
			                          		IdSystem = sys.solarSystemID
			                          	}).ToList();

			var systemsJumps = (from system in nomSysIdSys
			            join sysJump in listSystemJump
							on system.IdSystem equals sysJump.Key
			            select new
			                   	{
									nomSystems = system.NomSystem,
									nbreJump = sysJump.Value
			                   	}).ToList();

			// Maintenant il faut mettre à jour tout les UserControls.
			// Pour chaque userControl
			foreach (var child in wrapRoot.Children)
			{
				var ucTest = child as UcMarketItem;

				var totalJump = systemsJumps.Where(x => x.nomSystems.Equals(ucTest.lblGeo.Content)).Sum(y => y.nbreJump);
				ucTest.lblJump.Content = totalJump.ToString();

				ucTest.IsOkJump = true;

				if (ucTest.IsOkMarket && ucTest.IsOkKill && ucTest.IsOkJump)
					ucTest.IsEnabled = true;
			}

		}

		/// <summary>
		/// 
		/// </summary>
		/// <param name="sender"></param>
		/// <param name="e"></param>
		private void backgroundWorkerSystemsKill_DoWork(object sender, DoWorkEventArgs e)
		{
			//  solarSystemID="30001343" shipKills="0" factionKills="17" podKills="0" 
			e.Result = InformationsMap.ContexteMapKill;
		}

		/// <summary>
		/// 
		/// </summary>
		/// <param name="sender"></param>
		/// <param name="e"></param>
		private void backgroundWorkerSystemsKill_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
		{
			EveIndusEntities nouveauCOntexte = new EveIndusEntities();
			//  solarSystemID="30001343" shipKills="0" factionKills="17" podKills="0" 
			List<Tuple<int, int, int, int>> listSystemKill = e.Result as List<Tuple<int, int, int, int>>;

			var nomSysIdSys = (from sys in nouveauCOntexte.mapSolarSystems
							   select new
							   {
								   NomSystem = sys.solarSystemName,
								   IdSystem = sys.solarSystemID
							   }).ToList();


			var systemsKills = (from dd in nomSysIdSys
								join pp in listSystemKill
			            	on dd.IdSystem equals pp.Item1
			            select new
			                   	{
			                   		NomSysteme = dd.NomSystem,
			                   		shipsKills = pp.Item2,
			                   		npcKill = pp.Item3,
			                   		podKill = pp.Item4
			                   	}).ToList();
			
			// Maintenant il faut mettre à jour tout les UserControls.
			// Pour chaque userControl
			foreach (var child in wrapRoot.Children)
			{
				var ucTest = child as UcMarketItem;

				ucTest.lblShipKill.Content = systemsKills.Where(x => x.NomSysteme.Equals(ucTest.lblGeo.Content)).Sum(y => y.shipsKills).ToString(CultureInfo.InvariantCulture);
				ucTest.lblNpcKill.Content = systemsKills.Where(x => x.NomSysteme.Equals(ucTest.lblGeo.Content)).Sum(y => y.npcKill).ToString(CultureInfo.InvariantCulture);
				ucTest.lblPodKill.Content = systemsKills.Where(x => x.NomSysteme.Equals(ucTest.lblGeo.Content)).Sum(y => y.podKill).ToString(CultureInfo.InvariantCulture);

				ucTest.IsOkKill = true;

				if (ucTest.IsOkMarket && ucTest.IsOkKill && ucTest.IsOkJump)
					ucTest.IsEnabled = true;
			}
		}


		#endregion

	}
}
